"""
下面代码的核心目标：自动化地为一束花的详细信息生成一段详细、吸引人且营销导向的文字描述
代码逻辑清晰地分为四个阶段：模型加载 -> 管道封装 -> 提示工程 -> 执行推理
"""
import transformers
import torch
from langchain_community.llms import HuggingFacePipeline
from langchain_core.prompts import PromptTemplate

# 指定预训练模型的名称
model = r"D:\ideaSpace\MyPython\models\qwen\Qwen1.5-0.5B-Chat"

"""创建一个文本生成的管道：
使用 transformers 库的 pipeline API，这是一个高级抽象，它封装了模型加载、分词、推理、解码等复杂步骤
"""
pipeline = transformers.pipeline(
    "text-generation",        # 指定任务类型：文本生成
    model=model,              # 指定模型路径（从本地加载）
    torch_dtype=torch.float16, # 使用半精度浮点数，大幅减少显存占用，加快推理速度
    device_map="auto",        # 自动分配模型层到可用的GPU/CPU上，支持多卡
    max_length=1000           # 模型生成的最大token长度（包括输入和输出）
)

"""创建HuggingFacePipeline实例：将 Hugging Face 的 pipeline 对象包装成一个 LangChain 的 LLM 对象
目的是让Hugging Face 的模型能够无缝接入LangChain的框架，利用 LangChain 的提示模板、链（Chain）、代理（Agent）等强大功能
"""
llm = HuggingFacePipeline(pipeline=pipeline,
                          model_kwargs={'temperature':0})

"""定义一个字符串模板，该模板用于生成花束的描述，其中包含一个占位符 {flower_details}。
PromptTemplate 会正式化这个模板，并声明需要传入的变量名。目的是指导模型的行为。好的提示词是获得理想输出的关键。
"""
template = """
              为以下的花束生成一个详细且吸引人的描述：
              花束的详细信息：
              ```{flower_details}```
           """
prompt = PromptTemplate(template=template,
                        input_variables=["flower_details"])

"""构建链并执行推理 (LCEL)
构建链（Chain）：使用 LangChain 表达式语言（LCEL），通过 | 操作符将 prompt 和 llm 连接起来。
  这创建了一个可运行的序列：输入 -> 提示模板（填充占位符）-> 语言模型（生成文本）-> 输出
调用链（Invoke）：llm_chain.invoke(flower_details) 是执行这个序列的入口。它将用户输入的 flower_details 字符串传递给链。
  链首先将flower_details的值插入到提示模板的 {flower_details} 占位符中，组合成最终的、完整的提示词。
  然后将这个完整的提示词传递给Qwen模型。
  模型根据提示词生成描述文本。
  最后，invoke 方法返回模型的生成结果
"""
llm_chain = prompt | llm
# 需要生成描述的花束的详细信息
flower_details = "12支红玫瑰，搭配白色满天星和绿叶，包装在浪漫的红色纸中。"
# 打印生成的花束描述 - 使用invoke替代run
print(llm_chain.invoke(flower_details))